package net.googlecode.demenkov.controllers;

import net.googlecode.demenkov.domains.Person;
import net.googlecode.demenkov.domains.Vote;
import net.googlecode.demenkov.services.PersonService;
import net.googlecode.demenkov.utils.VoteComparatorByDate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

import javax.servlet.http.HttpServletRequest;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

/**
 * Controller for actions with votes
 *
 * @author Demenkov Yura
 */
@Controller
public class VoteController {
    @Autowired
    private PersonService personService;

    /**
     * Gets authorizated person's email
     *
     * @return person's email
     */
    private String getUserEmail() {
        Object principal = SecurityContextHolder.getContext().getAuthentication().getPrincipal();
        return ((UserDetails) principal).getUsername();
    }

    /**
     * Votes for a person
     *
     * @param personId of person to vote for
     * @return person's page with rised rating
     */
    @RequestMapping(value = "/persons/{personId}/addvote", method = RequestMethod.POST)
    public String voteForPerson(@PathVariable("personId") int personId) {
        Person personFrom = personService.findPersonByEmail(getUserEmail());
        Person personTo = personService.getPerson(personId);
        if (!personFrom.getPersonsAreVotedByThisPerson().contains(personTo)) {
            personService.createVote(personFrom, personTo);
        }
        return "redirect:/persons/" + personId;
    }

    /**
     * Deletes your vote for this person
     *
     * @param personId of person to delete vote
     * @return person's page with decreased rating
     */
    @RequestMapping(value = "/persons/{personId}/deletevote", method = RequestMethod.POST)
    public String deleteVoteForPerson(@PathVariable("personId") int personId) {
        Person personFrom = personService.findPersonByEmail(getUserEmail());
        Person personTo = personService.getPerson(personId);
        if ((personFrom.getPersonsAreVotedByThisPerson().contains(personTo)) && (personFrom.getPersonId() != personTo.getPersonId())) {
            personService.deleteVote(personFrom, personTo);
        }
        return "redirect:/persons/" + personId;
    }

    /**
     * Looks for persons that have voted for you
     *
     * @param request with parametrs for view-page
     * @return page with list of people that have voted for you
     */
    @RequestMapping(value = "/persons/whovotedforme")
    public String getPersonsThatVotedForMe(HttpServletRequest request) {
        Person person = personService.findPersonByEmail(getUserEmail());
        List<Vote> votes = new ArrayList<Vote>(person.getVotesTo());
        Collections.sort(votes, new VoteComparatorByDate());
        request.setAttribute("votes", votes);
        return "/whovoteme";
    }

}
